package com.gd.iot.energy.service.datamanage.impl;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.gd.iot.energy.code.ResponseCode;
import com.gd.iot.energy.consts.SystemConsts;
import com.gd.iot.energy.dao.datamanage.SysconfigTaskPOMapper;
import com.gd.iot.energy.exception.MyException;
import com.gd.iot.energy.po.datamanage.SysconfigTaskPO;
import com.gd.iot.energy.pojo.common.vo.ColumnVO;
import com.gd.iot.energy.pojo.common.vo.PageVO;
import com.gd.iot.energy.pojo.dailymanage.dto.EquipmentInstructionTreeSaveDTO;
import com.gd.iot.energy.pojo.dailymanage.vo.EquipmentInstructionTreeVO;
import com.gd.iot.energy.pojo.datamanage.dto.SysconfigTaskSaveDTO;
import com.gd.iot.energy.pojo.datamanage.vo.SysconfigTaskPageVO;
import com.gd.iot.energy.pojo.datamanage.vo.SysconfigTaskVO;
import com.gd.iot.energy.pojo.systemadmin.vo.EnumVO;
import com.gd.iot.energy.pojo.systemadmin.vo.EquipConcentVO;
import com.gd.iot.energy.pojo.systemadmin.vo.EquipmentmodelVO;
import com.gd.iot.energy.service.dailymanage.EquipmentInstructionTreeService;
import com.gd.iot.energy.service.datamanage.SysconfigTaskService;
import com.gd.iot.energy.service.systemadmin.EquipConcentService;
import com.gd.iot.energy.service.systemadmin.EquipmentmodelService;
import com.gd.iot.energy.util.CustomBeanUtils;
import com.gd.iot.energy.util.CustomColumnUtil;
import com.gd.iot.energy.util.CustomStrUtil;
import com.gd.iot.energy.util.EnergyTypeUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;

@Service
public class SysconfigTaskServiceImpl extends ServiceImpl<SysconfigTaskPOMapper, SysconfigTaskPO> implements SysconfigTaskService {
    @Resource
    private SysconfigTaskPOMapper sysconfigTaskPOMapper;

    @Autowired
    private EquipmentmodelService equipmentmodelService;

    @Autowired
    private EquipConcentService equipConcentService;

    @Autowired
    private EquipmentInstructionTreeService equipmentInstructionTreeService;

    /**
     * 表头文件
     */
    private static final String TASK_LIST_COLUMN_FILE_NAME = "datamanage/task_list.column";

    @Override
    public List<SysconfigTaskVO> getSysconfigTaskVOs(Long equipId, String name) {
        QueryWrapper<SysconfigTaskPO> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("equipment_id", equipId);
        queryWrapper.eq("is_del", SystemConsts.BooleanEnum.FALSE.value);
        if (StrUtil.isNotBlank(name)) {
            queryWrapper.like("name", name);
        }
        EnergyTypeUtil.injectEnergyTypeWrapper(queryWrapper);
        List<SysconfigTaskPO> sysconfigTaskPOS = sysconfigTaskPOMapper.selectList(queryWrapper);
        List<SysconfigTaskVO> sysconfigTaskVOS = new ArrayList<>(sysconfigTaskPOS.size());
        CustomBeanUtils.convertPojo(sysconfigTaskPOS,sysconfigTaskVOS,SysconfigTaskVO.class);
        return sysconfigTaskVOS;
    }

    @Override
    public PageVO<SysconfigTaskPageVO> getSysconfigTaskPageVOs(Long equipId, Integer filterType, String filterValue, Integer pageSize, Integer pageNo, String orderColumn, String orderType) {
        IPage<SysconfigTaskPO> page = new Page<>(pageNo, pageSize);
        QueryWrapper<SysconfigTaskPO> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("equipment_id", equipId);
        queryWrapper.eq("is_del", SystemConsts.BooleanEnum.FALSE.value);

        if (!SystemConsts.SysconfigTaskFilter.ALL.value.equals(filterType)) {
            if (SystemConsts.SysconfigTaskFilter.NAME.value.equals(filterType) && StrUtil.isNotBlank(filterValue)) {
                queryWrapper.like("name", filterValue.trim());
            }
        }
        if (StrUtil.isNotBlank(orderColumn) && StrUtil.isNotBlank(orderType)) {
            orderColumn = CustomStrUtil.humpToLine(orderColumn);
            queryWrapper.orderBy(true, orderType.equals(SystemConsts.OrderType.ASC.value), orderColumn);
        }
        EnergyTypeUtil.injectEnergyTypeWrapper(queryWrapper);
        IPage<SysconfigTaskPO> sysconfigTaskPOIPage = sysconfigTaskPOMapper.selectPage(page, queryWrapper);
        PageVO<SysconfigTaskPageVO> pageVO = new PageVO<>();
        pageVO.setPageSize(pageSize);
        pageVO.setPageNum(pageNo);
        List<SysconfigTaskPageVO> treePageVOS = convertToSysconfigTaskPageVOList(sysconfigTaskPOIPage.getRecords(), pageSize, pageNo);
        pageVO.setData(treePageVOS);
        pageVO.setTotal(sysconfigTaskPOIPage.getTotal());
        pageVO.setPages(sysconfigTaskPOIPage.getPages());

        //表头
        List<ColumnVO> columns = CustomColumnUtil.getColumn(TASK_LIST_COLUMN_FILE_NAME);
        pageVO.setColumns(columns);
        return pageVO;
    }

    /**
     * 对象转换
     *
     * @param records
     * @return
     */
    private List<SysconfigTaskPageVO> convertToSysconfigTaskPageVOList(List<SysconfigTaskPO> records, Integer pageSize, Integer pageNo) {
        List<EquipmentmodelVO> equipmentmodelVOs = equipmentmodelService.getEquipmentmodelVOs(null);
        Map<Long, EquipmentmodelVO> equipmentmodelVOMap = equipmentmodelVOs.stream().collect(
                Collectors.toMap(EquipmentmodelVO::getId, Function.identity(), (key1, key2) -> key2));

        List<EquipConcentVO> equipConcentVOs = equipConcentService.getEquipConcentVOs(null, null);
        Map<Long, EquipConcentVO> equipConcentVOMap = equipConcentVOs.stream().collect(
                Collectors.toMap(EquipConcentVO::getId, Function.identity(), (key1, key2) -> key2));

        List<EquipmentInstructionTreeVO> equipmentInstructionTreeVOs = equipmentInstructionTreeService.getEquipmentInstructionTreeVOs(null, null);
        Map<Long, EquipmentInstructionTreeVO> equipmentInstructionTreeVOMap = equipmentInstructionTreeVOs.stream().collect(
                Collectors.toMap(EquipmentInstructionTreeVO::getId, Function.identity(), (key1, key2) -> key2));

        List<SysconfigTaskPageVO> res = new ArrayList<>(records.size());
        SysconfigTaskPageVO sysconfigTaskPageVO;

        long i = pageSize * (pageNo - 1) + 1;
        for (SysconfigTaskPO record : records) {
            sysconfigTaskPageVO = new SysconfigTaskPageVO();
            sysconfigTaskPageVO.setSerialNum(i);
            sysconfigTaskPageVO.setId(record.getId());
            sysconfigTaskPageVO.setName(record.getName());
            sysconfigTaskPageVO.setEquipmentIdName(equipmentmodelVOMap.containsKey(record.getEquipmentId())
                    ? equipmentmodelVOMap.get(record.getEquipmentId()).getName() : "");
            StringBuilder sb = new StringBuilder();
            String[] split = record.getEquipConcents().split(",");
            for (String s : split) {
                String temp = equipConcentVOMap.containsKey(Long.valueOf(s)) ? equipConcentVOMap.get(Long.valueOf(s)).getConncentName() : "";
                sb.append(temp).append(",");
            }
            sb.deleteCharAt(sb.length() - 1);
            sysconfigTaskPageVO.setEquipConcents(sb.toString());
            sysconfigTaskPageVO.setTreeIdName(SystemConsts.TreeNameEnum.getValuenameByValue(BigDecimal.valueOf(record.getTreeId()).intValue()));
            sysconfigTaskPageVO.setTimeCron(record.getTimeCron());
            res.add(sysconfigTaskPageVO);
            i++;
        }
        return res;
    }

    @Override
    public Long add(SysconfigTaskSaveDTO taskSaveDTO) {
        if (taskSaveDTO.getEquipmentId() == null || taskSaveDTO.getEquipConcents() == null || taskSaveDTO.getTreeId() == null) {
            throw new MyException(ResponseCode.PARAMETER_REQUIRED);
        }

        SysconfigTaskPO sysconfigTaskPO = new SysconfigTaskPO();
        sysconfigTaskPO.setCompanyId(0L);
        sysconfigTaskPO.setCreateDate(new Date());
        sysconfigTaskPO.setEnergyType(SystemConsts.EnergyTypeEnum.WATER.value);
        sysconfigTaskPO.setIsDel(SystemConsts.BooleanEnum.FALSE.value);
        sysconfigTaskPO.setModifyDate(new Date());
        sysconfigTaskPO.setOperatorId(1L);

        sysconfigTaskPO.setEquipConcents(taskSaveDTO.getEquipConcents());
        sysconfigTaskPO.setEquipmentId(taskSaveDTO.getEquipmentId());
        sysconfigTaskPO.setTaskId(taskSaveDTO.getTaskId());
        sysconfigTaskPO.setTreeId(taskSaveDTO.getTreeId());
        sysconfigTaskPO.setTimeCron(taskSaveDTO.getTimeCron());
        EquipmentInstructionTreeSaveDTO equipmentInstructionTree = equipmentInstructionTreeService.getEquipmentInstructionTree(
                BigDecimal.valueOf(taskSaveDTO.getTaskId()).intValue());
        sysconfigTaskPO.setName(equipmentInstructionTree.getTreeName());
        sysconfigTaskPO.setState(0);
        sysconfigTaskPO.setType(0);

        sysconfigTaskPOMapper.insert(sysconfigTaskPO);
        return sysconfigTaskPO.getId();
    }

    @Override
    public boolean update(SysconfigTaskSaveDTO taskSaveDTO) {
        if (taskSaveDTO.getEquipmentId() == null || taskSaveDTO.getEquipConcents() == null || taskSaveDTO.getTreeId() == null) {
            throw new MyException(ResponseCode.PARAMETER_REQUIRED);
        }

        SysconfigTaskPO sysconfigTaskPO = new SysconfigTaskPO();
        sysconfigTaskPO.setId(taskSaveDTO.getId());
        sysconfigTaskPO.setModifyDate(new Date());
        sysconfigTaskPO.setOperatorId(1L);

        sysconfigTaskPO.setEquipConcents(taskSaveDTO.getEquipConcents());
        sysconfigTaskPO.setEquipmentId(taskSaveDTO.getEquipmentId());
        sysconfigTaskPO.setTaskId(taskSaveDTO.getTaskId());
        sysconfigTaskPO.setTreeId(taskSaveDTO.getTreeId());
        sysconfigTaskPO.setTimeCron(taskSaveDTO.getTimeCron());
        EquipmentInstructionTreeSaveDTO equipmentInstructionTree = equipmentInstructionTreeService.getEquipmentInstructionTree(
                BigDecimal.valueOf(taskSaveDTO.getTaskId()).intValue());
        sysconfigTaskPO.setName(equipmentInstructionTree.getTreeName());
        sysconfigTaskPO.setState(null);
        sysconfigTaskPO.setType(null);

        sysconfigTaskPOMapper.updateById(sysconfigTaskPO);
        return true;
    }

    @Override
    public boolean delete(List<Integer> ids) {
        if(CollUtil.isEmpty(ids)){
            throw new MyException(ResponseCode.PARAMETER_REQUIRED);
        }

        //供应商表逻辑删除
        QueryWrapper<SysconfigTaskPO> queryWrapper = new QueryWrapper<>();
        queryWrapper.in("id", ids);
        EnergyTypeUtil.injectEnergyTypeWrapper(queryWrapper);
        SysconfigTaskPO sysconfigTaskPO = new SysconfigTaskPO();
        sysconfigTaskPO.setIsDel(SystemConsts.BooleanEnum.TRUE.value);
        int num = sysconfigTaskPOMapper.update(sysconfigTaskPO,queryWrapper);

        return num > 0;
    }

    @Override
    public SysconfigTaskSaveDTO getSysconfigTask(Integer id) {
        SysconfigTaskPO sysconfigTaskPO = sysconfigTaskPOMapper.selectById(id);
        if(sysconfigTaskPO==null||SystemConsts.BooleanEnum.TRUE.value.equals(sysconfigTaskPO.getIsDel())){
            throw new MyException(ResponseCode.RECORD_NOT_EXIST);
        }

        SysconfigTaskSaveDTO sysconfigTaskSaveDTO = new SysconfigTaskSaveDTO();
        sysconfigTaskSaveDTO.setId(sysconfigTaskPO.getId());
        sysconfigTaskSaveDTO.setEquipmentId(sysconfigTaskPO.getEquipmentId());
        sysconfigTaskSaveDTO.setEquipConcents(sysconfigTaskPO.getEquipConcents());
        sysconfigTaskSaveDTO.setTaskId(sysconfigTaskPO.getTaskId());
        sysconfigTaskSaveDTO.setTreeId(sysconfigTaskPO.getTreeId());
        sysconfigTaskSaveDTO.setTimeCron(sysconfigTaskPO.getTimeCron());

        return sysconfigTaskSaveDTO;
    }

    @Override
    public SysconfigTaskPO getSysconfigTaskPO(Long id) {
        SysconfigTaskPO sysconfigTaskPO = sysconfigTaskPOMapper.selectById(id);
        if(sysconfigTaskPO==null||SystemConsts.BooleanEnum.TRUE.value.equals(sysconfigTaskPO.getIsDel())){
            throw new MyException(ResponseCode.RECORD_NOT_EXIST);
        }
        return sysconfigTaskPO;
    }

    @Override
    public Map<String, List<EnumVO>> getEnums() {
        Map<String, List<EnumVO>> resultMap = new HashMap<>();

        List<EnumVO> sysconfigTask = new ArrayList<>();
        for (SystemConsts.SysconfigTaskFilter value : SystemConsts.SysconfigTaskFilter.values()) {
            EnumVO vo = new EnumVO();
            vo.setValue(value.value);
            vo.setValueName(value.valueName);
            sysconfigTask.add(vo);
        }

        List<EnumVO> treeNameEnum = new ArrayList<>();
        for (SystemConsts.TreeNameEnum value : SystemConsts.TreeNameEnum.values()) {
            EnumVO vo = new EnumVO();
            vo.setValue(value.value);
            vo.setValueName(value.valueName);
            treeNameEnum.add(vo);
        }

        resultMap.put("sysconfigTask", sysconfigTask);
        resultMap.put("treeNameEnum", treeNameEnum);
        return resultMap;
    }
}
